/**
 * Copyright (c) 2007, Blue Hole Software. All rights reserved.
 * Code licensed under the Apache 2.0 License:
 * http://www.apache.org/licenses/
 */
package org.bhf.security.util;

import org.bhf.security.common.FullName;
import org.bhf.security.common.LoginID;
import org.bhf.security.common.Role;
import org.bhf.security.common.UserID;

import javax.security.auth.Subject;
import java.io.PrintStream;
import java.util.Map;

/**
 * Utility class containing methods for dumping information
 * about a <code>Subject</code>.
 * @exclude
 */
public final class SubjectUtil
{
    /**
     * Do not instantiate.
     */
    private SubjectUtil() { }

    /**
     * Copies the <code>Principals</code>, public and private credentials
     * of the specified <code>Subject</code> into a new <code>Subject</code>
     * that is not marked "read-only".
     *
     * @param subject the target <code>Subject</code>.  Must not be <code>null</code>.
     * @return a copy of the specified <code>Subject</code> that is not read-only.
     * @throws IllegalArgumentException if <code>subject == null</code>.
     */
    public static Subject   copySubject( final Subject subject )
    {
        if( subject == null )
            throw new IllegalArgumentException( "subject == null" );

        final Subject newSubject = new Subject();

        {
            newSubject.getPrincipals().addAll( subject.getPrincipals() );
            newSubject.getPublicCredentials().addAll( subject.getPublicCredentials() );
            newSubject.getPrivateCredentials().addAll( subject.getPrivateCredentials() );
        }

        return newSubject;
    }
    /**
     * Outputs the <code>FullName</code>, <code>UserID</code>,
     * <code>LoginID</code>, and <code>Role</code>s of the specified
     * <code>Subject</code>.
     *
     * @param subject the <code>Subject</code> to dump.
     *      Must not be <code>null</code>.
     * @param out the <code>PrintStream</code> to which to dump output.
     *      Must not be <code>null</code>.
     *
     * @throws java.lang.IllegalArgumentException if <code>subject == null</code>
     *      or if <code>out == null</code>.
     */
    public static void      dumpSubject(
                                final Subject subject,
                                final PrintStream out
                            )
    {
        if( subject == null )
            throw new IllegalArgumentException( "subject == null" );
        if( out == null )
            throw new IllegalArgumentException( "out == null" );

        FullName    fullName    = FullName.getFullName( subject );
        UserID      userID      = UserID.getUserID( subject );
        LoginID     loginID     = LoginID.getLoginID( subject );
        Role[]      roles       = Role.getRoles( subject );

        out.println( "Subject: " );
        out.println( "    FullName: " + fullName.getName() );
        out.println( "    UserID: " + userID.getName() );
        out.println( "    LoginID: " + loginID.getName() );
        for( final Role role : roles )
        {
            out.println( "    Role: " + role.getName() );

            Map parameters = role.getParameters();
            for( final Object o : parameters.entrySet() )
            {
                Map.Entry entry = (Map.Entry) o;

                String parameterName = (String) entry.getKey();
                String[] parameterValues = (String[]) entry.getValue();

                out.print( "        Parameter: " + parameterName + " = " );
                for( int k = 0; k < parameterValues.length; k++ )
                {
                    if( k != 0 )
                        out.print( ", " );

                    out.print( parameterValues[k] );
                }
                out.println( "" );
            }
        }
    }

}


